<template>
  <!-- 组件外部的 form-item -->
  <div style="z-index: 100; border: 1px solid #ccc; width: 100%">
    <Toolbar style="border-bottom: 1px solid #ccc" :editor="editorRef" :defaultConfig="toolbarConfig" :mode="mode" />
    <Editor
      :style="{ height: props.height + 'px', overflowY: 'hidden' }"
      v-model="content"
      :defaultConfig="editorConfig"
      :mode="props.mode"
      @onCreated="handleCreated" />

    <a-modal style="z-index: 1000" v-model:visible="resourceVisible" :render-to-body="false" :width="1080" :footer="false" draggable>
      <template #title>资源选择器</template>
      <sa-resource v-model="list" multiple ref="resource" returnType="url" />
    </a-modal>
  </div>
</template>

<script setup>
import '@wangeditor/editor/dist/css/style.css'
import { onBeforeUnmount, ref, shallowRef, watch, computed } from 'vue'
import { Boot,DomEditor,SlateTransforms   } from '@wangeditor/editor'
import { Editor, Toolbar } from '@wangeditor/editor-for-vue'

import { useAppStore } from '@/store'
import commonApi from '@/api/common'
import file2md5 from 'file2md5'
import tool from '@/utils/tool'





const resourceVisible = ref(false)
const appStore = useAppStore()

const props = defineProps({
  modelValue: { type: String },
  component: Object,
  height: { type: Number, default: 300 },
  mode: { type: String, default: 'default' },
  customField: { type: String, default: undefined },
})

const emit = defineEmits(['update:modelValue', 'change'])

let registerWangEditorButtonFlag = appStore.appCurrentSetting.registerWangEditorButtonFlag

const list = ref([])
const resource = ref()

let content = computed({
  get() {
    return props.modelValue
  },
  set(value) {
    emit('update:modelValue', value)
  },
})

watch(
  () => content.value,
  (vl) => emit('change', vl)
)

watch(
  () => list.value,
  (imgs) => {
    let tmp = ''
    imgs.map((img) => {
      if (
        img.indexOf('.jpg') > -1 ||
        img.indexOf('.png') > -1 ||
        img.indexOf('.bmp') > -1 ||
        img.indexOf('.jpeg') > -1 ||
        img.indexOf('.svg') > -1 ||
        img.indexOf('.gif') > -1
      ) {
        const node = { type: 'image', src: img, href: '', alt: '', style: {}, children: [{ text: '' }] }
        editorRef.value.insertNode(node)
      }
    })

    resource.value.clearSelecteds()
    resourceVisible.value = false
  }
)

const editorRef = shallowRef()

const toolbarConfig = {}
// 移除排除视频上传按钮配置
// toolbarConfig.excludeKeys = ['group-video', 'insertImage']
toolbarConfig.excludeKeys = ['insertImage']

class MyButtonMenu {
	// 定义 ImageElement 类型
	
  constructor() {
    this.title = '资源选择器'
    this.tag = 'button'
  }

  //  获取菜单执行时的 value ，用不到则返回空 字符串或 false
  getValue(editor) {
    return ''
  }

  //  // 菜单是否需要激活（如选中加粗文本，“加粗”菜单会激活），用不到则返回 false
  isActive(editor) {
    return false
  }

  // 菜单是否需要禁用（如选中 H1 ，“引用”菜单被禁用），用不到则返回 false
  isDisabled(editor) {
    return false
  }

  // 点击菜单时触发的函数
  exec(editor, value) {
    editor.emit('click_menu')
  }
}

class ImageWidthMenu {
  constructor(width) {
    this.title = width || '70%'
    this.tag = 'button'
    this.width = width || '70%'
    // this.iconSvg = '<svg width="18" height="18" viewBox="0 0 1024 1024" xmlns="http://www.w3.org/2000/svg"><path d="M832 192H192c-17.7 0-32 14.3-32 32v576c0 17.7 14.3 32 32 32h640c17.7 0 32-14.3 32-32V224c0-17.7-14.3-32-32-32z m-40 560H232V264h560v488z" fill="#333"/></svg>'
  }

  getValue(editor) {
    return ''
  }

  // 获取选中的图片节点
  getSelectedNode(editor) {
    const { selection } = editor
    if (!selection) return null
    return DomEditor.getSelectedNodeByType(editor, 'image')
  }

  // 检查是否激活（当前宽度是否为指定宽度）
  isActive(editor) {
    return false
    // const node = this.getSelectedNode(editor)
    // if (!node) return false
    // return node.style.width === this.width
  }

  // 没有选中图片则禁用
  
  isDisabled(editor) {
    if (editor.selection == null) return true

    const imageNode = this.getSelectedNode(editor)
    if (imageNode == null) {
      // 选区未处于 image node ，则禁用
      return true
    }
    return false
  }

  exec(editor) {
    if (this.isDisabled(editor)) return

    const imageNode = this.getSelectedNode(editor)
    if (imageNode == null) return

    // 隐藏 hoverbar
    const hoverbar = DomEditor.getHoverbar(editor)
    if (hoverbar) hoverbar.hideAndClean()

    const { style = {} } = imageNode; // 假设 imageNode 是 ImageElement 类型
    const props = {
      style: {
        ...style,
        width: this.width, // 使用传入的 width 参数
        height: '', // 清空 height
      },
    };

    SlateTransforms.setNodes(editor, props, {
      match: n => DomEditor.checkNodeType(n, 'image'),
    })
  }
}
const menu1Conf = {
  key: 'menu1', // 定义 menu key ：要保证唯一、不重复（重要）
  factory() {
    return new MyButtonMenu()
  }
}
const imageWidth70Conf = {
  key: 'imageWidth70',
  factory() {
    return new ImageWidthMenu('70%')
  },
}
const imageWidth80Conf = {
  key: 'imageWidth80',
  factory() {
    return new ImageWidthMenu('80%')
  },
}
const imageWidth95Conf = {
  key: 'imageWidth95',
  factory() {
    return new ImageWidthMenu('95%')
  },
}
if (registerWangEditorButtonFlag === undefined || registerWangEditorButtonFlag === false) {
  Boot.registerMenu(menu1Conf)
  Boot.registerMenu(imageWidth70Conf)
  Boot.registerMenu(imageWidth80Conf)
  Boot.registerMenu(imageWidth95Conf)
  appStore.setRegisterWangEditorButtonFlag(true)
}

toolbarConfig.insertKeys = {
  index: 1, // 插入的位置，基于当前的 toolbarKeys
  keys: ['menu1'],
}

const editorConfig = {
  placeholder: '请输入内容...',
  MENU_CONF: {},
  hoverbarKeys: {
    // 在编辑器中，选中链接文本时，要弹出的菜单
    link: {
      menuKeys: [
        // 默认的配置可以通过 `editor.getConfig().hoverbarKeys.image` 获取
        'imageWidth30',
        'imageWidth50',
        'imageWidth100',
        '|', // 分割符
        'imageFloatNone', // 增加 '图片浮动' 菜单
        'imageFloatLeft',
        'imageFloatRight',
        '|', // 分割符
        'editImage',
        'viewImageLink',
        'deleteImage',
      ],
    },image: {
		      menuKeys: [
	             'imageWidth30',
	             'imageWidth50',
				 'imageWidth70',
				 'imageWidth80',
				 'imageWidth95',
	             'imageWidth100',
	             'editImage',
	             'viewImageLink',
	             'deleteImage',
	      ],
		  }
  },
}

editorConfig.MENU_CONF['uploadImage'] = {
  async customUpload(file, insertFn) {
    uploadRequest(file, 'image', 'uploadImage').then((res) => {
      insertFn(tool.attachUrl(res.url))
    })
  },
}

// 配置视频上传
editorConfig.MENU_CONF['uploadVideo'] = {
  async customUpload(file, insertFn) {
    uploadRequest(file, 'video', 'uploadVideo').then((res) => {
      insertFn(tool.attachUrl(res.url))
    })
  },
  maxFileSize: 100 * 1024 * 1024, // 最大视频文件大小 100MB
}

const uploadRequest = async (file, type, method, requestData = {}) => {
  const hash = await file2md5(file)
  const dataForm = new FormData()
  dataForm.append(type, file)
  dataForm.append('isChunk', false)
  dataForm.append('hash', hash)
  for (let name in requestData) {
    dataForm.append(name, requestData[name])
  }
  const response = await commonApi[method](dataForm)
  return response.data
}

const handleCreated = (editor) => {
  editorRef.value = editor

  editorRef.value.on('click_menu', () => {
    resourceVisible.value = true
  })
}

onBeforeUnmount(() => {
  const editor = editorRef.value
  if (editor == null) return
  editor.destroy()
})
</script>

<style scoped></style>
<style>
/* 全局样式 */
.w-e-textarea-video-container {
  background: none !important;
  border: none !important;
  box-shadow: none !important;
}
</style>